package com.icebartech.core.interceptor;

import com.icebartech.core.enums.CommonResultCodeEnum;
import com.icebartech.core.exception.ServiceException;
import com.icebartech.core.vo.RespJson;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.validation.BindingResult;
import org.springframework.validation.ObjectError;
import org.springframework.web.HttpRequestMethodNotSupportedException;
import org.springframework.web.bind.MethodArgumentNotValidException;
import org.springframework.web.bind.MissingServletRequestParameterException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;

import java.util.Arrays;
import java.util.List;

@ControllerAdvice
public class MyControllerAdvice {

    private static Logger logger = LoggerFactory.getLogger(MyControllerAdvice.class);

    /**
     * 全局异常捕捉处理
     *
     * @param ex
     * @return
     */
    @ResponseBody
    @ExceptionHandler(value = Exception.class)
    public RespJson errorHandler(Exception ex) {
        int resultCode;
        StringBuilder errMsg = new StringBuilder();
        if (ex instanceof HttpRequestMethodNotSupportedException) {
            resultCode = 405;
            errMsg = new StringBuilder("不支持当前请求方式！请使用 " + Arrays.toString(((HttpRequestMethodNotSupportedException) ex).getSupportedMethods()) + " 方式请求");
        } else if (ex instanceof MissingServletRequestParameterException) {
            resultCode = CommonResultCodeEnum.MISSING_REQUIRED_ARGUMENTS.getCode();
            errMsg = new StringBuilder("缺少请求参数！ [" + ((MissingServletRequestParameterException) ex).getParameterType() + "]" + ((MissingServletRequestParameterException) ex).getParameterName());
        } else if (ex instanceof MethodArgumentNotValidException) {
            resultCode = CommonResultCodeEnum.INVALID_ARGUMENTS.getCode();
            BindingResult bindingResult = ((MethodArgumentNotValidException) ex).getBindingResult();
            List<ObjectError> allErrors = bindingResult.getAllErrors();
            for (ObjectError error : allErrors) {
                errMsg.append(error.getDefaultMessage()).append("\n");
            }
        } else if (ex instanceof ServiceException) {
            resultCode = Integer.parseInt(((ServiceException) ex).getErrorCode());
            errMsg = new StringBuilder(((ServiceException) ex).getErrorMessage());
        } else if (ex instanceof IllegalArgumentException) {
            // 断言抛出的异常，一般是函数入参有问题 抛出异常的地方必须在函数调用前进行参数校验
            resultCode = 500;
            errMsg = new StringBuilder("系统错误，请联系开发人员修改！" + ex.getMessage() + "!!!");
            ex.printStackTrace();
        } else {
            resultCode = 500;
            errMsg = new StringBuilder("未知错误！" + ex.getMessage() + "!!!");
            ex.printStackTrace();
        }

        RespJson respJson = new RespJson();
        respJson.setStatus(resultCode);
        respJson.setMsg(errMsg.toString());
        // logger.info("发生错误，errorMsg：" + ex.getMessage(), ex);
        return respJson;
    }

}